/*
 * Alloy Analyzer
 * Copyright (c) 2002 Massachusetts Institute of Technology
 *
 * The Alloy Analyzer is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * The Alloy Analyzer is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with the Alloy Analyzer; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */

package alloy.type;

import alloy.ast.LeafExpr;

/**
   Interface implemented by all basic types.  Note that we define
   a basic type as a type which can appear in a {@link RelationType}
   at some point during the analysis of an Alloy model.  Only a subset
   of basic types are "true" basic types, meaning that they can appear
   in a {@link RelationType} of an expression being translated to a boolean
   formula.  

   <p><em>NOTE:</em> only one BasicType object
   should be used for any given basic type, so that
   basic types can be compared for equality using
   object equality.
 */

public interface BasicType extends Comparable {

    /** <p>creates a new {@link LeafExpr} representing the
        set associated with this.
    */
    public LeafExpr toExpr();

    /** <p>Get the scope of this for the current command.
        <p><em>NOTE:</em> Only basic types which can be types of
        expressions in the final {@link alloy.ast.Formula} to be translated
        will implement this method.  Invoking this method on basic types
        which do not implement it should cause an error.
    */
    public int getScope();

    /** <p>Returns a name for an atom in the set associated with this.
        <p><em>NOTE:</em> Only basic types which can be types of
        expressions in the final {@link alloy.ast.Formula} to be translated
        will implement this method.  Invoking this method on basic types
        which do not implement it should cause an error.
        @param atom_ a number associated with the atom, which will be
        used to distinguish it in the atom name.
    */
    public String getAtomName(int atom_);

    /** <p>Returns the ith atom in the type.
        <p><em>NOTE:</em> Only basic types which can be types of
        expressions in the final {@link alloy.ast.Formula} to be translated
        will implement this method.  Invoking this method on basic types
        which do not implement it should cause an error.
        @param i: the index of the atom in the type, from zero to scope-1.
    */
    public alloy.api.Atom getAtom(int i);

    /** Return the name of the type, using shorter unqualified
	signature names where this does not create ambiguity. */
    public String toShortString();

    /**
     * Determines whether this is a subtype
     * of another BasicType. 
     * @param other input type 
     * @return true if this is a transitive subtype
     * of <tt>other</tt>.  Otherwise, returns false.
     **/
    public boolean isSubtypeOf(BasicType other); 

    /**
     * Computes the intersection of this and another
     * BasicType, if it exists.
     * @param other input type
     * @return a BasicType that represents the intersection of this
     * and <tt>other</tt>.  It returns an instance of EmptyType if 
     * this and other don't intersect.
     **/
    public BasicType intersect(BasicType other);


    /** @return true if this is an empty BasicType, otherwise returns false. **/
    public boolean isEmpty();

}
